import java.awt.BorderLayout;
import java.awt.EventQueue;
import java.awt.HeadlessException;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.PrintWriter;
import java.io.Serializable;
import java.net.URL;
import javax.swing.JApplet;
import javax.swing.JFrame;
import javax.swing.SwingUtilities;
import org.jfree.chart.ChartPanel;
import org.jfree.chart.JFreeChart;
import cx.ath.choisnet.io.SerializableHelper;
import cx.ath.choisnet.lang.ByteArrayBuilder;

/**
 *
 *
 */
public class ChartApplet
    extends JApplet
{
    private static final long serialVersionUID = 1L;

    /**
     * @throws HeadlessException
     */
    public ChartApplet() throws HeadlessException
    {
    }

    @Override
    public void init()
    {
        try {
            EventQueue.invokeAndWait( new Runnable() {
                @Override
                public void run()
                {
                    initComponents();
                }
            } );
        }
        catch( Exception ex ) {
            ex.printStackTrace();
        }
    }

    public void log( final String msg )
    {
        System.out.println( msg );
    }

    final public void log( final String msg, final Throwable e )
    {
        ByteArrayOutputStream   baos    = new ByteArrayOutputStream();
        PrintWriter             pw      = new PrintWriter( baos );

        pw.println( msg );
        e.printStackTrace( pw );
        pw.close();

        log( baos.toString() );
    }

    @Override
    public void start()
    {
        super.start();
    }

    @Override
    public void stop()
    {
        super.stop();
    }

    @Override
    public void destroy()
    {
        super.destroy();
    }

    private void initComponents()
    {
        String urlString = getParameter( "url" );

        log( "URLStr = " + urlString );

        if( urlString == null ) {
            urlString = "http://127.0.0.1:8080/bip/ChartObject";
            log( "URLStr (fallback) = " + urlString );
            }

        log( "getCodeBase()     = " + getCodeBase() );
        log( "getDocumentBase() = " + getDocumentBase() );

        try {
            URL         url     = new URL( urlString );
            JFreeChart  chart   = downloadObject( url, JFreeChart.class );

            log( "URL        = " + url );
            log( "JFreeChart = " + chart );

            // add the chart to a panel...
            final ChartPanel chartPanel = new ChartPanel( chart );
            //chartPanel.setPreferredSize(new java.awt.Dimension(500, 270));
            log( "ChartPanel = " + chartPanel );

            setContentPane( chartPanel );
            }
        catch( IOException e ) {
            log( "IOException", e );
            }
        catch( ClassNotFoundException e ) {
            log( "ClassNotFoundException", e );
            }
        catch( Exception e ) {
            log( "Exception ?", e );

            throw new RuntimeException( e );
            }

        setSize( 640, 480 );
    }

    protected byte[] download( final URL url ) throws IOException
    {
        ByteArrayBuilder bab = new ByteArrayBuilder();

        bab.append( url.openStream() );

        return bab.array();
    }

    protected <T extends Serializable> T downloadObject( final URL url, final Class<T> clazz )
        throws  IOException,
                ClassNotFoundException
    {
        return SerializableHelper.toObject( download( url ), clazz );
    }

    /**
     *
     */
    public static void main( String[] args )
    {
        SwingUtilities.invokeLater( new Runnable() {
            @Override
            public void run()
            {
                ChartApplet applet = new ChartApplet();
                JFrame frame = new JFrame();
                frame.add( applet, BorderLayout.CENTER );
                frame.setDefaultCloseOperation( JFrame.EXIT_ON_CLOSE );
                frame.setTitle( "ChartApplet" );
                frame.pack();
                frame.setLocationRelativeTo( null );
                frame.setVisible( true );
            }
        } );
    }


}
